<?php

namespace Cephalopod\SSL;

use Cephalopod\HttpTube;
use SplQueue;

class Context
{
    public bool $isClientServerConnection = false;

    public int $lastHeartBeatSendTime = 0;

    public int $lastHeartBeatRecvTime = 0;

    public int $lastDataRecvTime = 0;

    public bool $isFirstMessage = true;

    public int $contextBelongsToId = 0;

    public int $dataSentToId = 0; // always 0 if isClientServerConnection is true

    public OptimizedUnpackTube $optimizedUnpackTube;

    public string $dataToBeWritten = '';

    public array $browserIdInfoMap = [];

    public array $websiteIdBrowserIdMap = [];

    private string $residualData = '';

    public function __construct(string $privateKey = '')
    {
        $this->optimizedUnpackTube = new OptimizedUnpackTube();
        $this->optimizedUnpackTube->setPrivateKey($privateKey);
    }

    public function unpack(string &$data, bool $justPlaintext = true)
    {
        $this->optimizedUnpackTube->enqueue($data);
        $protocolData = $this->optimizedUnpackTube->dequeue();
        if ('' === $protocolData) {
            return [];
        }
        $unpackResult = Protocol::unpack($protocolData, null, $this->residualData);
        $this->residualData = $unpackResult['residual_data'];
        if (empty($unpackResult['origin_datas'])) {
            return [];
        }
        foreach ($unpackResult['origin_datas'] as &$plaintextInfo) {
            if ($justPlaintext) {
                yield $plaintextInfo['client_id'] => $plaintextInfo['plaintext'];
            } else {
                yield [$plaintextInfo['client_id'], $plaintextInfo['control_flag'], $plaintextInfo['plaintext']];
            }
        }
    }
}
